use serde::Deserialize;

#[derive(Debug, Deserialize, Clone)]
pub struct ServerConfig {
    pub host: String,
    pub port: u16,
    pub workers: usize,
}

#[derive(Debug, Deserialize, Clone)]
pub struct HuaweiCloudConfig {
    pub base_url: String,
    pub access_token: String,
    pub project_id: String,
    pub timeout_secs: u64,
}

#[derive(Debug, Deserialize, Clone)]
pub struct OPCUAConfig {
    pub namespace_uri: String,
    pub endpoint_url: String,
    pub security_policy: String,
}

#[derive(Debug, Deserialize, Clone)]
pub struct Config {
    pub server: ServerConfig,
    pub huawei_cloud: HuaweiCloudConfig,
    pub opcua: OPCUAConfig,
    pub logging: LoggingConfig,
}

#[derive(Debug, Deserialize, Clone)]
pub struct LoggingConfig {
    pub level: String,
    pub format: Option<String>,
    pub file_path: Option<String>,
    pub max_file_size_mb: Option<u32>,
    pub max_files: Option<u32>,
    pub enable_console: Option<bool>,
}

impl Config {
    pub fn load() -> Result<Self, config::ConfigError> {
        config::Config::builder()
            .add_source(config::File::with_name("config/default"))
            .add_source(config::Environment::with_prefix("OPCUA"))
            .build()?
            .try_deserialize()
    }
    
    pub fn server_address(&self) -> String {
        format!("{}:{}", self.server.host, self.server.port)
    }
}